#!/usr/bin/env python3
# -*- coding: utf-8 -*-
# @Time   : 2025-03-10 9:21:04
# @Author : 搬砖客

import os
from common.get_logger import GetLogger

from common.path_setting import ensure_path_sep
from common.testcase_template import write_testcase_file
from common.yaml_util import YamlUtil
from common.get_all_files_path import get_all_files

_SLASH = os.sep

log = GetLogger.get_logger()


class TestCaseAutomaticGeneration:
    """自动生成自动化测试中的test_case代码"""

    def __init__(self):
        pass

    @classmethod
    def case_data_path(cls) -> str:
        """返回 yaml 用例文件路径"""
        case_date_path = os.path.join(ensure_path_sep("\\data\\"))
        return case_date_path

    @classmethod
    def case_path(cls) -> str:
        """ 存放用例代码路径"""
        case_path = os.path.join(ensure_path_sep("\\testcases\\"))
        return case_path

    def file_name(self, file: str) -> str:
        """
        通过xlsx文件的命名，将名称转换成 py文件的名称
        :param file: 测试用例数据的文件路径
        :return:  示例： cs_imotorlinx\get_uuid.py
        """
        i = len(self.case_data_path())
        xls_path = file[i:]
        file_name = None
        # 路径转换
        if '.xlsx' in xls_path:
            file_name = xls_path.replace('.xlsx', '.py')
        elif '.xls' in xls_path:
            file_name = xls_path.replace('.xls', '.py')
        return file_name

    def get_case_path(self, file_path: str) -> tuple:
        """
        根据 excel 中的用例，生成对应 testCase 层代码的路径
        :param file_path: yaml用例路径
        :return: F:\\ShunYunAutoTest\\testcases\\cs_imotorlinx\\test_get_uuid.py', 'test_get_uuid.py'
        """

        # 这里通过“\\” 符号进行分割，提取出来文件名称
        path = self.file_name(file_path).split(_SLASH)
        # 判断生成的 testcase 文件名称，需要以test_ 开头
        case_name = path[-1] = path[-1].replace(path[-1], "test_" + path[-1])
        new_name = _SLASH.join(path)
        return self.case_path() + new_name, case_name

    def get_test_class_title(self, file_path: str) -> str:
        """
        自动生成类名称
        :param file_path:
        :return: sup_apply_list --> SupApplyList
        """
        # 提取文件名称
        fuc_name = os.path.split(self.file_name(file_path))[1][:-3]
        name = fuc_name.split("_")
        # 将文件名称格式，转换成类名称: sup_apply_list --> SupApplyList
        for i in range(len(name)):
            #  capitalize()将字符串的第一个字母变成大写,其他字母变小写。
            name[i] = name[i].capitalize()
        class_name = "".join(name)

        return class_name

    @classmethod
    def error_message(cls, param_name, file_path):
        """
        用例中填写不正确的相关提示
        :return:
        """
        msg = f"用例中未找到 {param_name} 参数值，请检查新增的用例中是否填写对应的参数内容" \
              "如已填写，可能是 yaml 参数缩进不正确\n" \
              f"用例路径: {file_path}"
        return msg

    def func_title(self, file_path: str) -> str:
        """
        函数名称
        :param file_path: yaml 用例路径
        :return:
        """
        file_name = os.path.split(self.file_name(file_path))[1][:-3]
        return file_name


    def mk_dir(self, file_path: str) -> None:
        """ 判断生成自动化代码的文件夹路径是否存在，如果不存在，则自动创建 """
        case_dir_path = os.path.split(self.get_case_path(file_path)[0])[0]
        if not os.path.exists(case_dir_path):
            os.makedirs(case_dir_path)

    def ensure_testcases_init_files(self) -> None:
        """确保 testcases 目录及其所有子目录都包含 __init__.py 文件"""
        # 规范化路径
        testcases_dir = ensure_path_sep("\\testcases\\")

        # 检查目录是否存在
        if not os.path.exists(testcases_dir):
            os.makedirs(testcases_dir)
            log.info(f"创建目录: {testcases_dir}")

        # 确保 testcases 根目录有 __init__.py
        init_path = os.path.join(testcases_dir, '__init__.py')
        if not os.path.exists(init_path):
            with open(init_path, 'w', encoding='utf-8') as f:
                pass
            log.info(f"创建文件: {init_path}")

        # 遍历所有子目录并确保每个目录都有 __init__.py
        for root, dirs, files in os.walk(testcases_dir):
            for dir_name in dirs:
                dir_path = os.path.join(root, dir_name)
                init_path = os.path.join(dir_path, '__init__.py')

                if not os.path.exists(init_path):
                    with open(init_path, 'w', encoding='utf-8') as f:
                        pass
                    log.info(f"创建文件: {init_path}")


    def excel_path(self, file_path: str) -> str:
        """
        生成动态 excel 路径, 主要处理业务分层场景
        :param file_path: 如业务有多个层级, 则获取到每一层/test_demo/DateDemo.py
        :return: Login/utils.yaml
        """
        i = len(self.case_data_path())
        # 兼容 linux 和 window 操作路径
        yaml_path = file_path[i:].replace("\\", "/")
        return yaml_path

    def get_case_automatic(self) -> None:
        """ 自动生成 测试代码"""
        self.ensure_testcases_init_files()
        file_path = get_all_files(file_path=self.case_data_path(), excel_data_switch=True)
        for file in file_path:
            # 判断代理拦截的yaml文件，不生成test_case代码
            if 'proxy_data.yaml' not in file:
                # 判断用例需要用的文件夹路径是否存在，不存在则创建
                self.mk_dir(file)
                write_testcase_file(
                    class_title=self.get_test_class_title(file), func_title=self.func_title(file),
                    case_path=self.get_case_path(file)[0], testdata_path=self.excel_path(file),
                    file_name=self.get_case_path(file)[1])
        log.info("自动生成测试用例成功")


if __name__ == '__main__':
    TestCaseAutomaticGeneration().get_case_automatic()
    # da = TestCaseAutomaticGeneration().func_title("D:\\Project2024\\ui_gitee\\data\\auto_web_excel模板.xls")
    # print(da)
    # file_path = get_all_files(file_path=da, excel_data_switch=True)
    # print(file_path)
    # test = TestCaseAutomaticGeneration()
    # case_data_path = test.case_data_path()  # D:\Project2024\api_gitee\data
    # yaml_path = r"D:\Project2024\api_gitee\data\ksd\首页\restful_standard_kmo_electra_recent_view_list.yaml"
    # file_name = test.file_name(yaml_path)  # ksd\首页\restful_standard_kmo_electra_recent_view_list.py
    # test.mk_dir(r"D:\Project2024\api_gitee\data\ksd\首页\restful_standard_kmo_electra_recent_view_list.yaml")
    # file = r'D:\Project2024\api_gitee\data\ksd\首页\restful2.yaml'
    # case_data = YamlUtil.get_yaml_data(r'D:\\Project2024\\api_gitee\\data\\ksd\\首页\\restful2.yaml')
    # allure_feature = test.allure_feature(case_data, file)
    # print(allure_feature)
    # class_title = test.get_test_class_title(
    #     r'D:\Project2024\api_gitee\data\ksd\首页\restful_view_list.yaml')  # RestfulViewList
    # file_name2 = 'ksd\\首页\\restful_view_list.py'
    # a = os.path.split(file_name2)
    # print(a)
    # print('restful_view_list.py'[:-3])
